import { getAuthToken, clearLoginStatus } from './auth.js';

// 基础URL配置
const BASE_URL = 'http://localhost:9999/api';

// 是否正在刷新token的标志
let isRefreshing = false;
// 存储等待刷新的请求队列
let refreshSubscribers = [];

// 刷新token的方法
const refreshToken = async () => {
  try {
    const currentToken = getAuthToken();
    if (!currentToken) {
      throw new Error('No token available');
    }
    
    // 调用token刷新接口
    const response = await uni.request({
      url: `${BASE_URL}/auth/refresh-token`,
      method: 'POST',
      header: {
        'Authorization': `Bearer ${currentToken}`
      }
    });
    
    if (response.statusCode === 200 && response.data && response.data.success) {
      const { token, expiresIn } = response.data.data;
      const tokenExpire = Date.now() + expiresIn * 1000;
      
      // 保存新的token
      uni.setStorageSync('auth_token', token);
      uni.setStorageSync('token_expire', tokenExpire);
      
      return token;
    } else {
      throw new Error('Token refresh failed');
    }
  } catch (error) {
    // 刷新失败，清除登录状态
    clearLoginStatus();
    uni.$emit('tokenExpired');
    throw error;
  }
};

// 将请求添加到刷新队列
const addRefreshSubscriber = (callback) => {
  refreshSubscribers.push(callback);
};

// 通知所有等待的请求继续执行
const notifyRefreshSubscribers = (token) => {
  refreshSubscribers.forEach(callback => callback(token));
  refreshSubscribers = [];
};

// 统一的请求函数
const request = (options) => {
  // 合并基础URL
  if (!options.url.startsWith('http')) {
    options.url = BASE_URL + options.url;
  }
  
  // 设置默认请求头
  options.header = options.header || {};
  if (!options.header['Content-Type']) {
    options.header['Content-Type'] = 'application/json';
  }
  
  // 获取token并添加到请求头
  const token = getAuthToken();
  if (token) {
    options.header['Authorization'] = `Bearer ${token}`;
  }
  
  // 处理重试逻辑
  const originalRequest = options;
  
  return new Promise((resolve, reject) => {
    uni.request({
      ...options,
      success: (res) => {
        // 处理业务状态码
        if (res.statusCode === 200) {
          const data = res.data;
          if (data.success) {
            // 业务成功
            resolve(data);
          } else {
            // 业务失败
            reject(new Error(data.message || '请求失败'));
          }
        } else if (res.statusCode === 401) {
          // token过期，需要刷新
          const config = originalRequest;
          
          if (!isRefreshing) {
            isRefreshing = true;
            
            // 刷新token
            refreshToken()
              .then(newToken => {
                isRefreshing = false;
                notifyRefreshSubscribers(newToken);
                
                // 用新token重试当前请求
                config.header['Authorization'] = `Bearer ${newToken}`;
                request(config).then(resolve).catch(reject);
              })
              .catch(error => {
                isRefreshing = false;
                reject(error);
              });
          } else {
            // 如果已经在刷新token，则将请求加入队列等待
            return new Promise((resolve) => {
              addRefreshSubscriber((newToken) => {
                config.header['Authorization'] = `Bearer ${newToken}`;
                request(config).then(resolve);
              });
            }).then(resolve).catch(reject);
          }
        } else if (res.statusCode === 403) {
          // 权限不足
          reject(new Error('权限不足，请联系管理员'));
        } else if (res.statusCode === 500) {
          // 服务器错误
          reject(new Error('服务器内部错误，请稍后重试'));
        } else {
          // 其他错误
          reject(new Error(`请求失败: ${res.statusCode}`));
        }
      },
      fail: (err) => {
        // 网络错误处理
        if (err.errMsg && err.errMsg.includes('timeout')) {
          // 特别处理超时错误
          reject(new Error('网络请求超时，请检查网络连接后重试'));
        } else {
          reject(new Error(`网络请求失败: ${err.errMsg}`));
        }
      }
    });
  });
};

// 封装常用的请求方法
export const http = {
  get(url, params = {}, header = {}) {
    return request({
      url,
      method: 'GET',
      data: params,
      header
    });
  },
  
  post(url, data = {}, header = {}) {
    return request({
      url,
      method: 'POST',
      data,
      header
    });
  },
  
  put(url, data = {}, header = {}) {
    return request({
      url,
      method: 'PUT',
      data,
      header
    });
  },
  
  delete(url, params = {}, header = {}) {
    return request({
      url,
      method: 'DELETE',
      data: params,
      header
    });
  },
  
  // 上传文件
  upload(url, filePath, name = 'file', formData = {}, header = {}) {
    return new Promise((resolve, reject) => {
      const token = getAuthToken();
      if (token) {
        header['Authorization'] = `Bearer ${token}`;
      }
      
      uni.uploadFile({
        url: BASE_URL + url,
        filePath,
        name,
        formData,
        header,
        success: (res) => {
          try {
            const data = JSON.parse(res.data);
            if (data.success) {
              resolve(data);
            } else {
              reject(new Error(data.message || '上传失败'));
            }
          } catch (e) {
            reject(new Error('上传失败: ' + res.data));
          }
        },
        fail: (err) => {
          reject(new Error(`文件上传失败: ${err.errMsg}`));
        }
      });
    });
  }
};

export default http;